package com.huifer.wgx.service.impl;

import com.huifer.wgx.model.FieldLineEntity;
import com.huifer.wgx.model.FieldPointEntity;
import com.huifer.wgx.model.InteriorLineEntity;
import com.huifer.wgx.model.InteriorPointEntity;
import com.huifer.wgx.repository.FieldLineRepository;
import com.huifer.wgx.repository.FieldPointRepository;
import com.huifer.wgx.repository.InteriorLineRepository;
import com.huifer.wgx.repository.InteriorPointRepository;
import com.huifer.wgx.service.InterLineService;
import com.huifer.wgx.spec.PointLineTypeSpec;
import java.util.ArrayList;
import java.util.List;
import javax.persistence.criteria.CriteriaBuilder;
import javax.persistence.criteria.CriteriaQuery;
import javax.persistence.criteria.Predicate;
import javax.persistence.criteria.Root;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Sort;
import org.springframework.data.domain.Sort.Direction;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.stereotype.Service;

/**
 * <p>Title : InterLineServiceImpl </p>
 * <p>Description : </p>
 *
 * @author huifer
 * @date 2019-03-21
 */
@Service
public class InterLineServiceImpl implements InterLineService {

    @Autowired
    private FieldLineRepository fieldLineRepository;
    @Autowired
    private InteriorLineRepository interiorLineRepository;
    @Autowired
    private InteriorPointRepository interiorPointRepository;


    /**
     * 将外业线段转换成内业线段
     *
     * @param workId 工作id
     * @param personnelId 内业人员id
     * @return 内业线段
     */
    @Override
    public List<InteriorLineEntity> field2InterLine(Long workId, Long personnelId) {

        try {
            Specification<FieldLineEntity> spec = (Specification<FieldLineEntity>) (root, criteriaQuery, criteriaBuilder) -> criteriaBuilder
                    .equal(root.get("workId"), workId);
            List<FieldLineEntity> all = fieldLineRepository.findAll(spec);

            Specification<InteriorPointEntity> specP = (Specification<InteriorPointEntity>) (root, criteriaQuery, criteriaBuilder) -> criteriaBuilder
                    .equal(
                            root.get("workId"), workId);
            List<InteriorPointEntity> allInterPoint = interiorPointRepository.findAll(specP);
            List<InteriorLineEntity> line = field2InterLineStac(all, personnelId, allInterPoint);
            return interiorLineRepository.saveAll(line);
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }

    private List<InteriorLineEntity> field2InterLineStac(List<FieldLineEntity> all,
            Long personnelId, List<InteriorPointEntity> allInterPoint) {
        try {
            List<InteriorLineEntity> result = new ArrayList<>();
            for (int i = 0; i < all.size(); i++) {
                FieldLineEntity out = all.get(i);
                InteriorLineEntity inLine = new InteriorLineEntity();

                inLine.setInteriorLineStartPointName(out.getFieldLineStartPointName());
                inLine.setInteriorLineStartPointDeep(out.getFieldLineStartDeep());
                inLine.setInteriorLineEndPointName(out.getFieldLineEndPointName());
                inLine.setInteriorLineEndPointDeep(out.getFieldLineEndDeep());
                inLine.setInteriorLineDs(out.getFieldLineDs());
                inLine.setInteriorLineMaterial(out.getFieldLineMaterial());

                inLine.setInteriorLineType(PointLineTypeSpec
                        .lineType(out.getFieldLineStartPointName(),
                                out.getFieldLineEndPointName()).getDesc());

                // 关联关系
                inLine.setWorkId(out.getWorkId());
                inLine.setPersonnelId(personnelId);
                setStartEndId(inLine, allInterPoint);

                result.add(inLine);
            }
            return result;
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }


    private void setStartEndId(InteriorLineEntity entity, List<InteriorPointEntity> allInterPoint) {
        for (int i = 0; i < allInterPoint.size(); i++) {
            InteriorPointEntity inPoint = allInterPoint.get(i);
            if (inPoint.getInteriorPointName()
                    .equals(entity.getInteriorLineStartPointName())) {
                entity.setInteriorLineStartPointId(inPoint.getInteriorPointId());

            } else if (inPoint.getInteriorPointName()
                    .equals(entity.getInteriorLineEndPointName())) {
                entity.setInteriorLineEndPointId(inPoint.getInteriorPointId());
            }
        }
    }

    /**
     * 保存内业线段
     *
     * @param iLine 内业线段
     * @return 内业线段
     */
    @Override
    public InteriorLineEntity saveOne(InteriorLineEntity iLine) {
        try {
            return interiorLineRepository.save(iLine);
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }

    /**
     * 更新内业线段
     *
     * @param iLine 内业线段
     * @return 内业线段
     */
    @Override
    public InteriorLineEntity updateiLine(InteriorLineEntity iLine) {
        try {
            return interiorLineRepository.save(iLine);
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }

    /**
     * 查询所有
     *
     * @param pageNum 页面号
     * @param pageSize 页面大小
     * @return 内业线段
     */
    @Override
    public Page<InteriorLineEntity> findAll(Integer pageNum, Integer pageSize) {
        return getInteriorLineEntity(pageNum, pageSize, null);
    }

    /**
     * 根据工程id查询所有
     *
     * @param pageNum 页面号
     * @param pageSize 页面大小
     * @param workId 工程id
     * @return 内业线段结果
     */
    @Override
    public Page<InteriorLineEntity> findByWorkId(Integer pageNum, Integer pageSize, Long workId) {
        Specification<InteriorLineEntity> spec = (Specification<InteriorLineEntity>) (root, criteriaQuery, criteriaBuilder) -> criteriaBuilder
                .equal(root.get("workId"), workId);

        return getInteriorLineEntity(pageNum, pageSize, spec);
    }

    /**
     * 根据内业人员id查询所有
     *
     * @param personnelId 采集人id
     * @param pageNum 页面号
     * @param pageSize 页面大小
     * @return 内业线段结果
     */
    @Override
    public Page<InteriorLineEntity> findByPersonnelId(Long personnelId, Integer pageNum,
            Integer pageSize) {
        Specification<InteriorLineEntity> spec = (Specification<InteriorLineEntity>) (root, criteriaQuery, criteriaBuilder) -> criteriaBuilder
                .equal(root.get("personnelId"), personnelId);
        return getInteriorLineEntity(pageNum, pageSize, spec);
    }

    /**
     * 获取全部内业线段
     *
     * @param pageNum 页面号
     * @param pageSize 页面大小
     * @param spec 条件
     * @return 内业线段
     */
    private Page<InteriorLineEntity> getInteriorLineEntity(Integer pageNum, Integer pageSize,
            Specification<InteriorLineEntity> spec) {
        Sort sort = new Sort(Direction.DESC, "interiorLineId");
        Pageable pageable = PageRequest.of(pageNum - 1, pageSize, sort);
        return interiorLineRepository.findAll(spec, pageable);
    }
}
